package com.xt.wikiperfumapi.Controller.perfume;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.github.pagehelper.PageInfo;
import com.github.pagehelper.page.PageMethod;
import com.xt.wikiperfumapi.model.*;
import com.xt.wikiperfumapi.model.vo.PerfumeVo;
import com.xt.wikiperfumapi.model.vo.RestBean;
import com.xt.wikiperfumapi.model.wrapper.PerfumerWrapper;
import com.xt.wikiperfumapi.service.impl.*;
import com.xt.wikiperfumapi.util.JwtUtil;
import jakarta.annotation.Resource;
import jakarta.servlet.http.HttpServletRequest;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.beanutils.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

@RequestMapping("/api/perfume")
@RestController
@Slf4j
public class PerfumeController {

    @Resource
    PerfumerWrapper perfumerWrapper;

    @Autowired
    JwtUtil jwtUtil;

    @Resource
    PerfumeInfoServiceImpl perfumeInfoService;

    @Resource
    PerfumeIngredientRefServiceImpl perfumeIngredientRefService;


    @Resource
    UserCollectPerfumeRefServiceImpl userCollectPerfumeRefService;

    @Resource
    PerfumeViewInfoServiceImpl perfumeViewInfoService;
    @Autowired
    private PerfumeCommentInfoServiceImpl perfumeCommentInfoServiceImpl;
    @Autowired
    private IngredientInfoServiceImpl ingredientInfoServiceImpl;

    /**
     * 获取香水详情，并携带香料
     * @param id
     * @param request
     * @return
     */
    @RequestMapping("/get/{id}")
    public RestBean getById(@PathVariable long id, HttpServletRequest request) {
        String uuid = jwtUtil.getJwtUUID(request);
        try {
            PerfumeInfo byId = perfumeInfoService.getById(id);
            PerfumeViewInfo perfumeViewInfo=new PerfumeViewInfo();
            perfumeViewInfo.setPerfumeId(id);
            perfumeViewInfo.setUserId(uuid);
            perfumeViewInfoService.save(perfumeViewInfo);//保存浏览记录
            return RestBean.success(perfumerWrapper.perfumeToVo(byId, uuid));
        } catch (Exception e) {
            log.info(e.getMessage());
            return RestBean.failure(400, "不存在该香水");
        }
    }

    /**
     * 列表查询香水
     *
     * @param page          页码
     * @param size          条数
     * @param brandId       品牌id
     * @param sex           性别
     * @param priceStart    价格区间开始
     * @param priceEnd      价格区间结束
     * @param name          香水名称
     * @param fragranceNote 香调
     * @param rankUptime    根据上线时间排序
     * @param rankBuy       根据销量排序
     * @param rankPrice     根据价格排序
     * @return
     */
    @RequestMapping("/list/{page}/{size}")
    public RestBean list(@PathVariable int page, @PathVariable int size,
                         Long brandId, String sex, BigDecimal priceStart,
                         BigDecimal priceEnd, String name, String fragranceNote,
                         Long rankUptime, Long rankBuy, Long rankPrice,HttpServletRequest request) {
        String uuid = jwtUtil.getJwtUUID(request);

        PageInfo perfumeInfoPageInfo = perfumeInfoService.queryByPage(page, size, brandId, sex, priceStart
                , priceEnd, name, fragranceNote, rankUptime, rankBuy, rankPrice);

        List<PerfumeInfo> perfumeInfos = perfumeInfoPageInfo.getList();

        List<PerfumeVo> perfumeVos=new ArrayList<>();
        perfumeInfos.forEach(el->{
            PerfumeVo perfumeVo=new PerfumeVo();
            try {
                BeanUtils.copyProperties(perfumeVo,el);
            }catch (Exception e){
                log.info(e.getMessage());
            }
            long count = userCollectPerfumeRefService.count(new QueryWrapper<UserCollectPerfumeRef>()
                    .eq("perfume_id", el.getPerfumeId())
                    .eq("user_id", uuid)
                    .eq("is_deleted",0)
            );
            perfumeVo.setUserCollect(count == 1);
            perfumeVos.add(perfumeVo);
            PerfumeViewInfo perfumeViewInfo=new PerfumeViewInfo();
            perfumeViewInfo.setPerfumeId(el.getPerfumeId());
            perfumeViewInfo.setUserId(uuid);
            perfumeViewInfoService.save(perfumeViewInfo);//保存浏览记录
        });
        perfumeInfoPageInfo.setList(perfumeVos);
        return RestBean.success(perfumeInfoPageInfo);
    }

    @RequestMapping("/latest")
    public RestBean latestUptime(HttpServletRequest request){
        String uuid = jwtUtil.getJwtUUID(request);
        List<PerfumeInfo> perfumeInfos = perfumeInfoService.list(new QueryWrapper<PerfumeInfo>()
                .eq("is_deleted", 0)
                .orderByDesc("year")
                .orderByDesc("perfume_id")
                .last("limit 20")
        );
        List<PerfumeVo> perfumeVos=new ArrayList<>();
        perfumeInfos.forEach(el->{
            PerfumeVo perfumeVo=new PerfumeVo();
            try {
                BeanUtils.copyProperties(perfumeVo,el);
            }catch (Exception e){
                log.info(e.getMessage());
            }
            long count = userCollectPerfumeRefService.count(new QueryWrapper<UserCollectPerfumeRef>()
                    .eq("perfume_id", el.getPerfumeId())
                    .eq("user_id", uuid)
                    .eq("is_deleted",0)
            );
            perfumeVo.setUserCollect(count == 1);
            perfumeVos.add(perfumeVo);
        });
        return RestBean.success(perfumeVos);
    }

    @RequestMapping("/viewMax")
    public RestBean viewMax(HttpServletRequest request){
        String uuid = jwtUtil.getJwtUUID(request);
        List<PerfumeViewInfo> perfumeViewInfos = perfumeViewInfoService.list(
                new QueryWrapper<PerfumeViewInfo>()
                        .select("perfume_id", "COUNT(*) as viewCount") // 选择香水ID和访问次数
                        .groupBy("perfume_id")                         // 按香水ID分组
                        .orderByDesc("viewCount")                      // 按访问次数降序排序
                        .last("limit 20")                              // 限制返回记录数为20
        );
        List<PerfumeVo> perfumeVos=new ArrayList<>();
        perfumeViewInfos.forEach(el->{
            PerfumeInfo byId = perfumeInfoService.getById(el.getPerfumeId());
            PerfumeVo perfumeVo=new PerfumeVo();
            try {
                BeanUtils.copyProperties(perfumeVo,byId);
            }catch (Exception e){
                log.info(e.getMessage());
            }
            long count = userCollectPerfumeRefService.count(new QueryWrapper<UserCollectPerfumeRef>()
                    .eq("perfume_id", byId.getPerfumeId())
                    .eq("user_id", uuid)
                    .eq("is_deleted",0)
            );
            perfumeVo.setUserCollect(count == 1);
            perfumeVos.add(perfumeVo);
        });
        return RestBean.success(perfumeVos);
    }

    @RequestMapping("/ings/query")
    public RestBean queryByIngredients(@RequestBody List<Long> ingredientIds) {
        // 创建查询条件
        QueryWrapper<PerfumeIngredientRef> queryWrapper = new QueryWrapper<>();
        queryWrapper
                .select("perfume_id")  // 只选择 perfume_id
                .in("ingredient_id", ingredientIds)  // 根据成分 ID 筛选
                .eq("is_deleted", 0)  // 过滤掉已删除的记录
                .groupBy("perfume_id")  // 按 perfume_id 分组
                .having("COUNT(DISTINCT ingredient_id) = {0}", ingredientIds.size());  // 确保香水包含所有指定的成分

        // 执行查询
        List<PerfumeIngredientRef> result = perfumeIngredientRefService.list(queryWrapper);

//        // 提取 perfume_id 列表
//        List<Long> perfumeIds = result.stream()
//                .map(PerfumeIngredientRef::getPerfumeId)
//                .collect(Collectors.toList());
        List<PerfumeInfo> perfumeInfos=new ArrayList<>();
        result.forEach(el->{
            perfumeInfos.add(perfumeInfoService.getById(el.getPerfumeId()));
        });

        // 返回结果
        return RestBean.success(perfumeInfos);
    }


    @RequestMapping("/comment")
    public RestBean CommentToPerfume(@RequestBody PerfumeCommentInfo perfumeCommentInfo,
                                     HttpServletRequest request){
        String uuid = jwtUtil.getJwtUUID(request);
        perfumeCommentInfo.setUserId(uuid);
        perfumeCommentInfo.setInputTime(new Date());
        int size = perfumeCommentInfoServiceImpl.list().size();
        perfumeCommentInfo.setPerfumeCommentId((long)size);
        return perfumeCommentInfoServiceImpl.save(perfumeCommentInfo)?
                RestBean.success(perfumeCommentInfo):RestBean.failure(500,"server error");
    }
    @RequestMapping("/comment/remove/{id}")
    public RestBean removeCommentById(@PathVariable long id){
        try {
            PerfumeCommentInfo byId = perfumeCommentInfoServiceImpl.getById(id);
            if (byId.getIsDeleted()==1){
                return RestBean.failure(400,"该评论已删除");
            }
            byId.setIsDeleted(1);
            return perfumeCommentInfoServiceImpl.updateById(byId)?
                    RestBean.success(byId):RestBean.failure(500,"server error");
        }catch (Exception e){
            log.info(e.getMessage());
            return RestBean.failure(400,"不存在该评论信息");
        }
    }

//    @RequestMapping("/list/{page}/{item}")
//    public RestBean list(@PathVariable int page,@PathVariable int item,String  name){
//        PageMethod.startPage(page,item);
//        List<PerfumeInfo> brandInfos = perfumeInfoService.list(new QueryWrapper<PerfumeInfo>()
//                .eq("is_deleted",0)
//                .like("name",name)
//        );
//        return RestBean.success(new PageInfo<>(brandInfos));
//    }

    @RequestMapping("/update")
    public RestBean update(@RequestBody PerfumeInfo perfumeInfo){
        perfumeInfo.setUpdateTime(new Date());
        perfumeIngredientRefService.remove(new QueryWrapper<PerfumeIngredientRef>()
                .eq("perfume_id",perfumeInfo.getPerfumeId())
        );
        if (perfumeInfo.getIngredients().contains(",")) {
            String[] split = perfumeInfo.getIngredients().split(",");
            for (int i = 0; i < split.length; i++) {
            }
            savePerfumeRef(perfumeInfo.getPerfumeId(), split);
        } else {
            String[] split = perfumeInfo.getIngredients().split("，");
            savePerfumeRef(perfumeInfo.getPerfumeId(), split);
        }
        return perfumeInfoService.updateById(perfumeInfo)?
                RestBean.success(perfumeInfo):RestBean.failure(500,"server error");
    }

    @RequestMapping("/del/{id}")
    public RestBean del(@PathVariable long id){
        return perfumeInfoService.removeById(id)?
                RestBean.success():RestBean.failure(500,"server error");
    }

    @RequestMapping("/getId/{id}")
    public RestBean getById(@PathVariable long id){
        return RestBean.success(perfumeInfoService.getById(id));
    }

    @RequestMapping("/insert")
    public RestBean insert(@RequestBody PerfumeInfo perfumeInfo) {
        perfumeInfo.setInputTime(new Date());
        long size = perfumeInfoService.list().size()+1;
        perfumeInfo.setPerfumeId(size);
        if (perfumeInfo.getIngredients().contains(",")) {
            String[] split = perfumeInfo.getIngredients().split(",");
            savePerfumeRef(size, split);
        } else {
            String[] split = perfumeInfo.getIngredients().split("，");
            savePerfumeRef(size, split);
        }
        return perfumeInfoService.save(perfumeInfo)?RestBean.success()
                :RestBean.failure(500,"server error");

    }

    private void savePerfumeRef(long size, String[] split) {
        for (int i = 0; i < split.length; i++) {
            try {
                IngredientInfo ingredientInfo = ingredientInfoServiceImpl.getOne(new QueryWrapper<IngredientInfo>()
                        .eq("name", split[i])
                );
                PerfumeIngredientRef perfumeIngredientRef = new PerfumeIngredientRef();
                perfumeIngredientRef.setIngredientId(ingredientInfo.getIngredientId());
                perfumeIngredientRef.setPerfumeId(size);
                perfumeIngredientRefService.save(perfumeIngredientRef);
            } catch (Exception e) {
                log.info(e.getMessage());
            }
        }
    }
}
